package com.xc.easyExcel;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.xc.exception.BusinessException;
import com.xc.pojo.WcPoint;
import com.xc.service.IWcPointService;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

/**
 * 这里不加泛型,是因为我遇到的项目是要分析excel的数据,没办法确定要读的excel的列有什么,有几条!
 */
@Component
public class CustomListener extends AnalysisEventListener {

    @Autowired
    private IWcPointService pointService;

    private List<TwWhShelfImportOutput> outputs = new ArrayList<>();
    StringBuilder errStr = new StringBuilder();
    Result result = new Result();

    // map代表一行，String是列索引，Object改行该列单元格元素
    @Override
    public void invoke(Object object, AnalysisContext analysisContext) {
        Map<Integer, Object> map = (Map) object;
        if (map.values().size() % 2 != 0) {
            throw new BusinessException(9999, "点位缺少");
        }
        //货架对象
        TwWhShelfImportOutput importOutput = new TwWhShelfImportOutput();
        // 固定数据
        importOutput.setAreaName(map.get(0).toString());
        importOutput.setCode(map.get(1).toString());
        importOutput.setType(map.get(2).toString());
        importOutput.setName(map.get(3).toString());
        // 点位集合
        // map无法获取流与for遍历，keySet转为key：value的entity的Set集合，得到对象用get获取key与value
        List<Long> pointIds = map.entrySet().stream()
                // map是列号：单元格值的格式，列号是数字。第五个元素之后也就是列号为4及其之后
                .filter(m -> m.getKey() > 3)
                // 过滤掉为null、empty的值
                .filter(m -> ObjectUtil.isNotEmpty(m.getValue()))
                // 将之后的点位id转为Long值
                .map(m -> Long.valueOf(m.getValue().toString()))
                .toList();
        // 校验点位id是否存在
        List<WcPoint> list = pointService.list(new QueryWrapper<WcPoint>().lambda()
                .in(WcPoint::getFmsPathId, pointIds));
        List<Long> ids = list.stream().map(WcPoint::getFmsPathId).map(Long::valueOf).toList();
        List<Long> unPoints = new ArrayList<>(pointIds);
        // 点位不存在的打印输出
        if (unPoints.size() != ids.size()) {
            if (CollUtil.isNotEmpty(ids)) {
                unPoints.removeAll(ids);
            }
            for (Long point : unPoints) {
                // map的值作为kay，列号作为value。反转map(遇到重复key值了，没想到的)
                // Map<Object, Integer> reverseMap = map.entrySet().stream().collect(Collectors.toMap(Map.Entry::getValue, Map.Entry::getKey));
                for (int i = 0; i < pointIds.size(); i++) {
                    if (pointIds.get(i).equals(point)) {
                        errStr.append("第" + analysisContext.readRowHolder().getRowIndex() + "行，第" + (i + 4) + "列的点位" + point + "不存在").append("|");
                        break;
                    }
                }
            }
            result.errRows++;// 最好用get方法获取吧
            return;
        }
        importOutput.setList(pointIds);
        this.outputs.add(importOutput);
        result.successRows++;// 最好用get方法获取吧
    }

    @Override
    public void doAfterAllAnalysed(AnalysisContext analysisContext) {
        this.outputs.forEach(System.out::println);
        // 最好用get方法获取吧
        result.totalRows = result.errRows + result.successRows;
        System.out.println("总行数：" + result.totalRows);
        System.out.println("成功行数：" + result.successRows);
        System.out.println("失败行数：" + result.errRows);
        System.out.println(errStr.toString());
    }

    @Data
    public class Result {
        @Schema(title = "总行数")
        private int totalRows = 0;

        @Schema(title = "失败行数")
        private int errRows = 0;

        @Schema(title = "成功行数")
        private int successRows = 0;
    }
}
